<%@page import="com.sun.beans.finder.ClassFinder"%>
<%@page import="java.util.LinkedList"%>
<%@page import="java.util.Stack"%>
<%@page import="java.text.*"%>
<%@page import ="org.jfree.data.category.*"%>
<%@page import="java.io.*" %>
<%@page import="org.jfree.chart.*" %>
<%@page import="org.jfree.chart.servlet.ServletUtilities" %>
<%@page import="org.jfree.chart.entity.*" %>
<%@page import ="org.jfree.chart.JFreeChart"%>
<%@page import ="org.jfree.chart.plot.SpiderWebPlot" %>
<%@page import ="org.jfree.chart.title.*" %>
<%@page import ="org.jfree.ui.RectangleEdge" %>
<%@page language="java" contentType="text/html; charset=UTF-8"%>
<%@page import="javax.xml.parsers.DocumentBuilderFactory,javax.xml.parsers.DocumentBuilder,
					org.w3c.dom.*"%>
<%@page import ="java.util.*" %>
<%@page import ="ctm.javacode.MySpiderWebPlot" %>
<%@page import ="java.sql.*" %>
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">

<html xmlns="http://www.w3.org/1999/xhtml">
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8" />
<title>問卷</title>
<style type="text/css">
<!--
body {
	background-image: url(img/grass.jpg);
    background-position: center top;
	background-color: #FFFFFF;
	background-repeat: repeat;
}
body,td,th {
	color: #000000;
	font-size:24px;
	font-family: Arial;
}


a:link {
font-family:"標楷體"; 
	font-size:25px;
	text-decoration:none;
	color:#277C35;
	background-color:#FFFFFF;
}
a:visited {
	font-family:"標楷體"; 
	font-size:25px;
	text-decoration:none;
	color:#277C35;
	background-color:#FFFFFF;
}
a:hover {
font-family:"標楷體"; 
	font-size:25px;
	text-decoration:none;
	color:#000000;
	background-color:#FFFFFF;
}


.ind:link {
color: #535353;
text-decoration:none;
font-family:"標楷體";
font-size:18px;
}
.ind:visited {
color:#535353;
text-decoration:none;
font-family:"標楷體";
font-size:18px;
}

.ind:hover {
color:#BB280F;
text-decoration:none;
font-family:"標楷體";
font-size:18px;
}


.HEAD_STYLE {
	font-weight:bold;
	color: #1B4001;
	font-family:"標楷體";
	font-size:30px; 
}
.TEXT_STYLE {
	font-family:Arial;
	color:#193940;
	font-size:24px;
	font-weight:bold;
}
.BOTTOM_STYLE {
	color: #FFFFFF; 
	font-family: Arial; 
	font-size:20px;
}
.LEFT_BUTTON {
	font-family:"標楷體"; 
	font-size:30px;
}

-->
</style>

</head>
<body alink="#FF0000" vlink="#FF0000" onLoad="KW_doClock()">
<table width="100%" border="0">
		<tr>
			<td><p>&nbsp;</p></td>
		</tr>
				
			
			
		
 
    		<td width="5%">&nbsp;</td>
			
			<td bgcolor="#FFFFFF"><table width="100%" border="0">
      			<tr>
        			<td background="img/herbal.jpg">
						<p>&nbsp;</p>
          				<p>&nbsp;</p>
          				<p>&nbsp;</p>
          				<p>&nbsp;</p>
		  				<p>&nbsp;</p>
          
          			</td>
			  </tr>
     
	 
	 
	 
	  			  <tr>
        			<td>	
						<table bgcolor="#437A27" width="100%" border="0">
         					 <tr>
            					<td>&nbsp;</td>
           			 			
          			 		</tr>
        				</table>
					</td>
     			  </tr>
      
	  			
	  
	  
	  
	 			  <tr>
        				<td>
							<table width="100%">
           						<tr>
									<td valign="top">
										<table width="100%">
											
								
											<tr>
												
											<td>
<%	
	String category = request.getParameter("category");
	String path;
	if(category.equals("A")){
		path = "./WEB-INF/cal.xml";
	}
	else{
		path = "./WEB-INF/cal2.xml";
	}
	Document BookDom = null;
	String File = request.getRealPath(path);
	DocumentBuilderFactory factory = DocumentBuilderFactory.newInstance();
	
	try{
		DocumentBuilder builder = factory.newDocumentBuilder();
		
		BookDom = builder.parse(File);
		
	}catch(Exception e){
		out.print("XML analysis error" + e.getMessage());
	}
		
%>
<%!
	public boolean isTextNode(Node node){
		return node.getNodeName().equals("#text");
	}
%>
<% //讀取xml
	LinkedList<String> CLASS = new LinkedList<String>();//放體質型別
	LinkedList<String> CLASSforQ = new LinkedList<String>();//放各體質對應之題目
	LinkedList<String> QuesforType = new LinkedList<String>();/*NO USE*///放各體質對應之題目的分數計算type
	LinkedList<String> Originformula = new LinkedList<String>();//放原始分數計算的公式
	LinkedList<String> typeForOriFormula = new LinkedList<String>();//放原始分數公式對應的體質
	LinkedList<String> formula = new LinkedList<String>();//放轉化公式的計算式
	LinkedList<String> typeCondition = new LinkedList<String>();//放體質判斷的計算式
	LinkedList<String> type = new LinkedList<String>();//放要Print出來體質(滿足體質判斷計算式的話)
	
	Element element = BookDom.getDocumentElement();
	NodeList nodes1 = element.getChildNodes();
	for(int i=0;i < nodes1.getLength() ; i++){
		Node temp1 = nodes1.item(i);
		NamedNodeMap attrlist1 = temp1.getAttributes();
		if(attrlist1 != null)
		{
			//System.out.println(attrlist1.item(0).getNodeName());
			//System.out.println(attrlist1.item(0).getNodeValue());
		}
		if(isTextNode(temp1)){
			continue;
		}

		NodeList nodes2 = temp1.getChildNodes();
		for(int j=0;j < nodes2.getLength();j++){
			Node temp2 = nodes2.item(j);
			NamedNodeMap attrlist2 = temp2.getAttributes();
			if(attrlist2 != null && temp2.getNodeName() == "CLASS"){
				CLASS.add(attrlist2.item(0).getNodeValue());
				//System.out.println(attrlist2.item(0).getNodeName());
				//System.out.println(attrlist2.item(0).getNodeValue());
			}
	
			if(isTextNode(temp2)){
				continue;
			}
			if(temp2.getNodeName() == "formula_1"){
				formula.add(temp2.getFirstChild().getNodeValue());
				//System.out.println(formula);
			}
			if(temp2.getParentNode().getNodeName() == "TYPE_RESULT"){
				type.add(temp2.getNodeName());
				typeCondition.add(temp2.getFirstChild().getNodeValue());
				//System.out.println(type.pop());
				//System.out.println(typeCondition.pop());
			}
			if(temp2.hasChildNodes() && temp2.getNodeName() == "CLASS"){
				NodeList nodes3 = temp2.getChildNodes();
				for(int k=0; k<nodes3.getLength();k++){
					Node temp3 = nodes3.item(k);
					if(isTextNode(temp3)){
						continue;
					}
					CLASSforQ.add(temp3.getNodeName());
					//System.out.println(":"+CLASSforQ.pop());
					NamedNodeMap attrlist3 = temp3.getAttributes();		
					if(attrlist3 != null && temp3.getParentNode().getNodeName() == "CLASS"){
						QuesforType.add(attrlist3.item(0).getNodeValue());
						//System.out.println(">"+QuesforType.pop());
						//System.out.println(attrlist3.item(0).getNodeName());
						//System.out.println(attrlist3.item(0).getNodeValue());
					}
				}
				CLASSforQ.add("end");
				QuesforType.add("end");
				//System.out.println(":"+CLASSforQ.pop());
				//System.out.println(">"+QuesforType.pop());
			}
			if(temp2.getNodeName() == "ORI_Value"){
				NamedNodeMap attrlist4 = temp2.getAttributes();
				if(attrlist4 != null){
					typeForOriFormula.add(attrlist4.item(0).getNodeValue());
				}
				Originformula.add(temp2.getFirstChild().getNodeValue());
			}
	
		}	
	}
	/*for(int i=0;i<Originformula.size();i++){
		System.out.print(typeForOriFormula.get(i) + ":");
		System.out.println(Originformula.get(i));
	}*/
	//將讀進來的體質由中文轉變成英文(主要為了讀取radio按鈕的值)
	int typeCount = Integer.parseInt(request.getParameter("typeCount"));
	//System.out.println(typeCount);
	String alphabet = "ABCDEFGHIJKLMNOPQRSTUVWXYZ";
	LinkedList<String> CLASStoEng = new LinkedList<String>();//放型別(英文型式)
	for(int i=0 ; i < typeCount;i++){
		CLASStoEng.add(alphabet.substring(i, i+1));
	}
	//計算每個類型的題目數(轉化公式需要)
	LinkedList<Integer> questioncount = new LinkedList<Integer>();//放每個類別題目數
	int s=0,count=0;
	for(int i = 0; i<CLASS.size() ;i++){
		while(s < CLASSforQ.size()){
			if(CLASSforQ.get(s).equals("end")){
				questioncount.add(count);
				count=0;
				break;
			}
			s++;
			count++;
		}
		s++;
	}
	/*for(int i=0;i<questioncount.size();i++){
		System.out.println(questioncount.get(i));
	}*/
%>
<%	//計算各型別的原始分數
///////////////////////////////////////////////////user問卷紀錄insert到資料庫
	Class.forName("org.gjt.mm.mysql.Driver");
	Connection myConn= DriverManager.getConnection("jdbc:mysql://127.0.0.1/questiontable?user=root&password=891216aa");
	File userhistory = new File("C:/History/" + request.getSession().getAttribute("login") );
	userhistory.mkdir();
	java.util.Date date = new java.util.Date();
	String cate;
	if(category.equals("A")){
		cate = "A_";
	}
	else{
		cate = "B_";
	}
	String timeStamp = cate + Integer.toString(date.getYear() + 1900) + "_" + 
			Integer.toString(date.getMonth() + 1) + "_" +
			Integer.toString(date.getDate()) + "_" +
			Integer.toString(date.getHours()) + "_" +
			Integer.toString(date.getMinutes()) + "_" +
			Integer.toString(date.getSeconds());
	Statement state=myConn.createStatement();
	String sql = "Insert into history(name,filename,Questionnaire)values('"+request.getSession().getAttribute("login")+"','"+ timeStamp +"','"+category+"')";
	state.executeUpdate(sql);
	state.close();
	myConn.close();
	
	File file = new File(userhistory + "/" + timeStamp + ".xml");
	file.createNewFile();
	Writer writer = new BufferedWriter( new OutputStreamWriter(new FileOutputStream(userhistory + "/" + timeStamp + ".xml"), "UTF-8"));
	writer.write("<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n<body>\n\t<question>\n");
	
	
	int quesCount = Integer.parseInt(request.getParameter("quesCount"));
	for(int k=0;k<CLASStoEng.size();k++){
		for(int g=1;g<=quesCount;g++){
			if(request.getParameter("type"+CLASStoEng.get(k)+g) != null){
				writer.write("\t\t<" + "type"+CLASStoEng.get(k)+g+">"+request.getParameter("type"+CLASStoEng.get(k)+g)
							+"</"+"type"+CLASStoEng.get(k)+g+">\n");
			}
			else{
				continue;
			}
		}
	}
	writer.write("\t</question>\n");
////////////////////////////////////////////////////////////////////////////////
	LinkedList<Double> originValues = new LinkedList<Double>();//存各型別原始分數
	for(int i=0;i<typeForOriFormula.size();i++){
		double temp1,temp2,temp3;
		String operatorRE="(\\+|-|\\*|/|>|=|<|\\||&|!)+";
		Stack<Double> operation = new Stack<Double>();
		LinkedList<String> postfixTokenList = new LinkedList<String>();
		LinkedList<String> postfixTokenList2 = new LinkedList<String>();
		//公式轉成後序式
		postfixTokenList = InfixTransPostfix(Originformula.get(i));
		//System.out.println(postfixTokenList);
		postfixTokenList2 = assiagValue2(postfixTokenList,CLASStoEng,request);
		//System.out.println(postfixTokenList2);
		for(int j=0;j<postfixTokenList2.size();j++){
			if(postfixTokenList2.get(j).matches(operatorRE)){
				temp1=operation.pop();
				temp2=operation.pop();
				temp3=calculate(temp1,temp2,postfixTokenList2.get(j));
				operation.add(temp3);
			}
			else{
				operation.add(Double.parseDouble(postfixTokenList2.get(j)));
			}
		}
		originValues.add(operation.pop());
	}
	/*for(int i=0;i<originValues.size();i++){
		System.out.println(originValues.get(i));
	}	*/
%>
<% //處理轉化公式(轉成後序式)
	LinkedList<String> postfixTokenList = new LinkedList<String>();
	for(int i=0;i<formula.size();i++){
		postfixTokenList = InfixTransPostfix(formula.get(i));
	}
	//for(int i=0;i<postfixTokenList.size();i++)
	//	System.out.println(postfixTokenList.get(i));	
%>
<% //轉化公式的運算
	double temp1,temp2,temp3;
	String operatorRE="(\\+|-|\\*|/|>|=|<|\\||&|!)+";
	Stack<Double> operation = new Stack<Double>();
	LinkedList<String> postfixTokenList2 = new LinkedList<String>();
	LinkedList<Double> transValue = new LinkedList<Double>();
	for(int j=0;j<originValues.size();j++){
		postfixTokenList2 = assiagValue(postfixTokenList,originValues,questioncount,j);
		/*for(int i=0;i<postfixTokenList2.size();i++){
		System.out.println(postfixTokenList2.get(i));
		}
		System.out.println();*/
		for(int i=0;i<postfixTokenList2.size();i++){
			if(postfixTokenList2.get(i).matches(operatorRE)){
				temp1=operation.pop();
				temp2=operation.pop();
				temp3=calculate(temp1,temp2,postfixTokenList2.get(i));
				operation.add(temp3);
			}
			else{
				operation.add(Double.parseDouble(postfixTokenList2.get(i)));
			}
		}
		transValue.add(operation.pop());
	}
///////////////////////////////////////////////////user問卷紀錄寫至xml
	writer.write("\t<transValue>\n");
	for(int i=0;i<transValue.size();i++){
		writer.write("\t\t<" + CLASS.get(i) + ">" + transValue.get(i) + "</" + CLASS.get(i) + ">\n");
	}
	
	writer.write("\t</transValue>\n");
////////////////////////////////////////////////////////////////////////////////
	
%>
<%	//Show出雷達圖
	DefaultCategoryDataset dataset = new DefaultCategoryDataset();
	String group1="";
	
	int index=0;
	while(index < transValue.size() && index < CLASS.size()){
		dataset.addValue(transValue.get(index), group1 ,CLASS.get(index));
		index++;
	}
	MySpiderWebPlot spiderwebplot = new MySpiderWebPlot(dataset);
	JFreeChart jfreechart = new JFreeChart("", TextTitle.DEFAULT_FONT,spiderwebplot, false);
	final ChartRenderingInfo info = new ChartRenderingInfo(new StandardEntityCollection());
	LegendTitle legendtitle = new LegendTitle(spiderwebplot);
	legendtitle.setPosition(RectangleEdge.BOTTOM);
	jfreechart.addSubtitle(legendtitle);
	          String fname = ServletUtilities.saveChartAsJPEG(jfreechart, 600, 400, info, session);
	PrintWriter pw = new PrintWriter(out);
	ChartUtilities.writeImageMap(pw, fname, info, false);
	pw.flush();
	String chartURL = request.getContextPath() + "/servlet/DisplayChart?filename=" + fname;
%>
<% //根據轉化分來分類
	double[] tranValueTemp = new double[transValue.size()];
	String[] tranClassTemp = new String[CLASS.size()];
	LinkedList<String> post = new LinkedList<String>();
	String consti;
	for(int i = 0; i < type.size(); i++){
		post = InfixTransPostfix(typeCondition.get(i));
		//System.out.println(post);
		if(judge(post,transValue)){
			consti = type.get(i);
			tranValueTemp[i/2] = transValue.get(i/2);
			tranClassTemp[i/2] = consti;
		}
	}
////////////////////////////////////做sort
	boolean flag = true;
	for(int i = 0;i < tranValueTemp.length-1 && flag; i++){
		flag = false;
		for(int j = 0; j < tranValueTemp.length-i-1;j++){
			if(tranValueTemp[j+1] > tranValueTemp[j]){
				tranValueTemp = swap(tranValueTemp,j+1,j);
				tranClassTemp = swap(tranClassTemp,j+1,j);
				flag = true;
			}
		}
	}
////////////////////////////////////印出屬於哪種體質並將user問卷紀錄寫至xml
%>
<center><font class="HEAD_STYLE">體質自測結果:</font><br><br></center>
<%
	int typeCount2=1;
	writer.write("\t<typePrint>\n");
	for(int i=0;i<tranValueTemp.length;i++){
		if(tranValueTemp[i] != 0.0){
			writer.write("\t\t<type" + typeCount2 + ">" + tranClassTemp[i] + "</type" + typeCount2 + ">\n");
			typeCount2++;
%>
	<center><font style="font: bold normal bold 14pt/26pt '標楷體'"><%= tranClassTemp[i] %></font></center><br>		
<%						
		}
	}
	writer.write("\t</typePrint>\n</body>");
	writer.close();
	
%>
	<center><font color="3333FF" size="5" class="TEXT_STYLE" style="font: bold normal bold 16pt/28pt '標楷體'">體質自測雷達圖</font><br>
	</center>
	<center><IMG SRC="<%= chartURL %>" WIDTH="600" HEIGHT="400"
	BORDER="0" USEMAP="#<%= fname %>"></center>
<%!
	public boolean judge(LinkedList<String> post,LinkedList<Double> transValue){
		boolean flag = false;
		String temp1,temp2,temp3,temp4;
		String operatorRE="(\\+|-|\\*|/|>|=|<|\\||&|!)+";
		Stack<String> operation = new Stack<String>();
		LinkedList<String> assignpost = new LinkedList<String>();
		assignpost = assiagValue2(post,transValue);
		//System.out.println(assignpost);
		for(int i=0;i<assignpost.size();i++){
			if(assignpost.get(i).matches(operatorRE)){
				temp1 = operation.pop();
				temp2 = operation.pop();
				temp3 = calculate(temp1,temp2,assignpost.get(i));
				operation.add(temp3);
			}
			else{
				operation.add(assignpost.get(i));
			}
		}
		temp4 = operation.pop();
		if(temp4.equals("true"))
			flag = true;
		else
			flag = false;
		return flag;
	}
%>
<%!
	public double[] swap(double[] values,int i ,int j){
		double temp = values[i];
		values[i] = values[j];
		values[j] = temp; 
		return values;
	}
%>
<%!
	public String[] swap(String[] ClassTemp,int i ,int j){
		String temp = ClassTemp[i];
		ClassTemp[i] = ClassTemp[j];
		ClassTemp[j] = temp; 
		return ClassTemp;
	}
%>
<%!
	public LinkedList<String> assiagValue(LinkedList<String> postfixTokenList,LinkedList<Double> 
									originValues,LinkedList<Integer> questioncount,int j){
		LinkedList<String> temp = new LinkedList<String>();
		for(int i=0;i<postfixTokenList.size();i++){
			if(postfixTokenList.get(i).equals("ori")){
				temp.add(originValues.get(j).toString());
			}
			else if(postfixTokenList.get(i).equals("lists")){
				temp.add(questioncount.get(j).toString());
			}
			else{
				temp.add(postfixTokenList.get(i));
			}
		}
		return temp;
	}
%>
<%!
	public LinkedList<String> assiagValue2(LinkedList<String> post,LinkedList<Double> transValue){
		LinkedList<String> assignpost = new LinkedList<String>();
		for(int i=0;i<post.size();i++){
			if(post.get(i).equals("type_A")){
				assignpost.add(transValue.get(0).toString());
			}
			else if(post.get(i).equals("type_B")){
				assignpost.add(transValue.get(1).toString());
			}
			else if(post.get(i).equals("type_C")){
				assignpost.add(transValue.get(2).toString());
			}
			else if(post.get(i).equals("type_D")){
				assignpost.add(transValue.get(3).toString());
			}
			else if(post.get(i).equals("type_E")){
				assignpost.add(transValue.get(4).toString());
			}
			else if(post.get(i).equals("type_F")){
				assignpost.add(transValue.get(5).toString());
			}
			else if(post.get(i).equals("type_G")){
				assignpost.add(transValue.get(6).toString());
			}
			else if(post.get(i).equals("type_H")){
				assignpost.add(transValue.get(7).toString());
			}
			else if(post.get(i).equals("type_I")){
				assignpost.add(transValue.get(8).toString());
			}
			else{
				assignpost.add(post.get(i));
			}
		}
		return assignpost;
	}
%>
<%!	
	public LinkedList<String> assiagValue2(LinkedList<String> postfixTokenList,LinkedList<String> CLASStoEng,HttpServletRequest request){
		
		int k=0;
		LinkedList<String> temp = new LinkedList<String>();
		String operatorRE="(\\+|-|\\*|/|>|=|<|\\||&|!)+";
		for(int i=0;i<postfixTokenList.size();i++){
			if(postfixTokenList.get(i).matches(operatorRE)){
				temp.add(postfixTokenList.get(i));
			}
			else if(postfixTokenList.get(i).contains("Q")){
				String ques = postfixTokenList.get(i).substring(1);
				while(k < CLASStoEng.size()){
					if(request.getParameter("type"+CLASStoEng.get(k)+ques) != null){
						temp.add(request.getParameter("type"+CLASStoEng.get(k)+ques));
						k=0;
						break;
					}
					else{
						k++;
					}
				}
			}
			else{
				temp.add(postfixTokenList.get(i));
			}
		}
		return temp;
	}
%>
<%!
	public String calculate(String a,String b,String op){
		boolean temp,a1,b1;
		String cal="";
		if(op.equals(">")){
			temp = Double.parseDouble(b) >  Double.parseDouble(a);
			if(temp)
				cal = "true";
			else
				cal = "false";
		}
		else if(op.equals("<")){
			temp = Double.parseDouble(b) <  Double.parseDouble(a);
			if(temp)
				cal = "true";
			else
				cal = "false";
		}
		else if(op.equals(">=")){
			temp = Double.parseDouble(b) >=  Double.parseDouble(a);
			if(temp)
				cal = "true";
			else
				cal = "false";
		}
		else if(op.equals("<=")){
			temp = Double.parseDouble(b) <=  Double.parseDouble(a);
			if(temp)
				cal = "true";
			else
				cal = "false";
		}
		else if(op.equals("||")){
			if(a.equals("true"))
				a1 = true;
			else
				a1 = false;
			if(b.equals("true"))
				b1 = true;
			else
				b1 = false;
			
			temp = (b1 || a1);
			if(temp)
				cal = "true";
			else
				cal = "false";
		}
		else if(op.equals("&&")){
			if(a.equals("true"))
				a1 = true;
			else
				a1 = false;
			if(b.equals("true"))
				b1 = true;
			else
				b1 = false;
			
			temp = (b1 && a1);
			if(temp)
				cal = "true";
			else
				cal = "false";
		}
		else;
			
		return cal;
	}
%>
<%!
	public double calculate(double a,double b,String op){
		NumberFormat nf = NumberFormat.getInstance();
		nf.setMaximumFractionDigits(2);
		nf.setMinimumFractionDigits(2);
		double cal=0.0;
		char ch = op.charAt(0);
		switch(ch){
			case '+':
				cal = Double.parseDouble(nf.format(b+a));
				break;
			case '-':
				cal = Double.parseDouble(nf.format(b-a));
				break;
			case '*':
				cal = Double.parseDouble(nf.format(b*a));
				break;
			case '/':
				cal = Double.parseDouble(nf.format(b/a));
				break;
		}
		return cal;
	}
%>
<%!
	public LinkedList<String> InfixTransPostfix(String formula){
		LinkedList<String> infixTokenList = new LinkedList<String>();
		LinkedList<String> postfixTokenList = new LinkedList<String>();
		infixTokenList = cutToken(formula);
		postfixTokenList = translate(infixTokenList);
		return postfixTokenList;
	}
%>
<%!
	public LinkedList<String> cutToken(String formula){
	LinkedList<String> infixTokenList = new LinkedList<String>();
	String operatorRE="(\\+|-|\\*|/|>|=|<|\\||&|!)+";
	String token="";

	for(int i=0;i<formula.length();i++)
	{
		//取出字元
		String ch = formula.substring(i, i+1);
		String temp = token+ch;
					
		if(temp.matches("\\s+"))
		{
			//如果是空白不做事情
			token="";
			//System.out.println("space : "+temp);
			continue;
		}
		
		else if(temp.matches("\\(|\\)"))
		{
			token=temp;
			//System.out.println("operator : "+temp);

		}
		// + , * , | 是正規表示式 的 keyword 要加\\
		else if(temp.matches(operatorRE))
		{
			token=temp;
			//System.out.println("operator : "+temp);
		}
		else if(temp.matches("\\d+"))
		{
			token=temp;
			//System.out.println("digital : "+temp);
		}		
		else if(temp.matches("\\w+"))
		{
			token=temp;
			//System.out.println("word : "+temp);
		}
		else
		{
			//進到else 代表temp不是上面那4種可能 ，可能已經混到其他種字元
			//所以把token 放進List後 把token清空 並取i--再回到上一個開始測
			infixTokenList.add(token);
			//System.out.println("token : "+token);
			//System.out.println("else ch : "+ch);
			
			token="";
			i--;
		}
		
	}
	//如果最後不是空白 要印出來  不然要是語法會有錯誤
	if(!token.matches(""))
	{
		infixTokenList.add(token);
		//System.out.println("final token:"+token);
	}
	return infixTokenList;
}
%>
<%! 
	public LinkedList<String> translate(LinkedList<String> infixTokenList) {
	
		LinkedList<String> postfixTokenList = new LinkedList<String>();		

		Stack<String> operatorStack = new Stack<String>();
		for(String token:infixTokenList)
		{
			//如果是運算元
			if(token.matches("(\\w)+"))
			{
				//System.out.println("word : "+token);
				postfixTokenList.add(token);
			}
			else if(token.matches("\\)"))
			{
				//System.out.println("( : "+token);
				String operator=operatorStack.peek();//peek 即為 top
				while(!operator.matches("\\("))
				{				
					operatorStack.pop();
					postfixTokenList.add(operator);
					operator=operatorStack.peek();
				}//如果operator不是左括號	
				operatorStack.pop();//pop掉 (
			}
			else
			{
				//System.out.println("operator : "+token);
				//如果Stack 是空 就直接加入Stack
				if(operatorStack.empty())
				{
					operatorStack.push(token);
				}
				else
				{
					//Stack 裡 operator 優先權的判斷  token 和 Stack的top比較
					if(isTokenHeightPriority(token,operatorStack.peek()))
					{	
						//如果大於將token (operator)放入Stack中
						operatorStack.push(token);
					}
					else
					{
						//如果小於等於  pop stack的元素 直到 token (operator)的優先權 大於peek為止
						do
						{
							
							postfixTokenList.add(operatorStack.pop());		
							if(operatorStack.empty())
							{
								//如果Stack已經清空就跳出迴圈
								break;
							}
						}while(!isTokenHeightPriority(token,operatorStack.peek()));
						//pop完 後 再將token (operator)放入Stack中
						operatorStack.push(token);
					}
				}
			}
			
		}
		while(!operatorStack.empty())
		{
			postfixTokenList.add(operatorStack.pop());
		}
		/*
		for(String elm: postfixTokenList)
		{
			System.out.println("postfixTokenList token : "+elm);
		}*/
		
		return postfixTokenList;
	}
%>
<%!
		private boolean isTokenHeightPriority(String token, String peek) {
		// TODO Auto-generated method stub
		
		int tokenPriority = 0;
		int peekPriority = 0;
		
		if(token.matches("\\("))
		{
			tokenPriority=OperatorPriorityEnum.leftbracketOutStack.getPriority();
		}
		else if(token.matches("\\*|/"))
		{
			tokenPriority=OperatorPriorityEnum.multiDivide.getPriority();
		}		
		else if(token.matches("\\+|-"))
		{
			tokenPriority=OperatorPriorityEnum.addMinus.getPriority();
		}
		else if(token.matches("(!|>|<|=)+"))
		{
			tokenPriority=OperatorPriorityEnum.greaterSmallerEqual.getPriority();
		}
		else if(token.matches("(&|\\|)+"))
		{
			tokenPriority=OperatorPriorityEnum.andOr.getPriority();
		}
		
		
		if(peek.matches("\\("))
		{
			peekPriority=OperatorPriorityEnum.leftbracketInStack.getPriority();
		}
		else if(peek.matches("\\*|/"))
		{
			peekPriority=OperatorPriorityEnum.multiDivide.getPriority();
		}		
		else if(peek.matches("\\+|-"))
		{
			peekPriority=OperatorPriorityEnum.addMinus.getPriority();
		}
		else if(peek.matches("(!|>|<|=)+"))
		{
			peekPriority=OperatorPriorityEnum.greaterSmallerEqual.getPriority();
		}
		else if(peek.matches("(&|\\|)+"))
		{
			peekPriority=OperatorPriorityEnum.andOr.getPriority();
		}

		if(tokenPriority < peekPriority)
		{

			return true;
		}
		else
		{

			return false;
		}
	}
%>
<%!
	public enum OperatorPriorityEnum{
		
		leftbracketOutStack(0),
		
		multiDivide(1),
		
		addMinus(2),
		
		greaterSmallerEqual(3),
		
		andOr(4),
		
		leftbracketInStack(5);
		// 值愈小  優先權愈高
		private int priority;
		OperatorPriorityEnum(int priority)
		{
			this.priority = priority;
		}
		/**
		 * @return the priority
		 */
		public int getPriority() {
			return priority;
		}		
	}
%>


  
</td>
											</tr>
											<tr><td align="center">
											<button onClick="location = 'main.jsp'">返回首頁</button>	
											</td>
											</tr>
											
										</table>
									
             

		
											
								  </td>
									

								</tr>
       					 </table>
         

         				</td>
			  </tr>
   
	  
					 <tr>
      					  
   					    <td><p>&nbsp;</p></td>
  					 </tr>
	  				
					<tr>
      					  <td bgcolor="#437A27"><div align="center" class="BOTTOM_STYLE">Copyright@CCU_PLlab</div></td>
   
			  </tr>
    						
  	 			  
	
			</table>
		</td>
	    
		<td width="5%">&nbsp;</td>
</table>
<p>&nbsp;</p>
</body>
</html>
